#include "fenetre.h"
#include "ui_fenetre.h"
#include "configgame.h"

Fenetre::Fenetre(Client* c, MyThread* mt, QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Fenetre),
    _mythread(mt),
    _client(c)
{
    if (DEBUG) {std::cout << "debut creation fenetre" << std::endl;}

    ui->setupUi(this);

    newMsg(); // Pour savoir si connecte ou deconnecte

    scrAct = eDEF;
    defScreen = new DefaultScreen(ui->wEmp1);
    defScreen->show();

    QObject::connect(ui->bCreer, SIGNAL(clicked()), this, SLOT(createGame()));
    QObject::connect(ui->bQuitter, SIGNAL(clicked()), this, SLOT(quitter()));
    QObject::connect(ui->lineChat, SIGNAL(returnPressed()), this, SLOT(lineChatReturn()));

    QObject::connect(_mythread, SIGNAL(newClient()), this, SLOT(newClient()));
    QObject::connect(_mythread, SIGNAL(newGame()), this, SLOT(newGame()));
    QObject::connect(_mythread, SIGNAL(newMsg()), this, SLOT(newMsg()));
    QObject::connect(_mythread, SIGNAL(decoC()), this, SLOT(decoClient()));
    QObject::connect(_mythread, SIGNAL(decoP()), this, SLOT(decoGame()));
    QObject::connect(_mythread, SIGNAL(createGame()), this, SLOT(traitementCreateGame()));
    QObject::connect(_mythread, SIGNAL(addPartie()), this, SLOT(slotAddPartie()));
    QObject::connect(_mythread, SIGNAL(rmPartie()), this, SLOT(slotRmPartie()));
    QObject::connect(_mythread, SIGNAL(launch()), this, SLOT(slotLaunch()));

    if (DEBUG) {std::cout << "boutons connectes" << std::endl;}
    if (DEBUG) {std::cout << "envoie demande clients et parties" << std::endl;}

    sf::Packet p;
    p << eMAIN_ALLCLIENTS;
    _client->send(p, true);
    p.clear();
    p << eMAIN_ALLGAMES;
    _client->send(p, true);

    if (DEBUG) {std::cout << "fenetre construite" << std::endl;}
}

Fenetre::~Fenetre()
{
    delete ui;
}

void Fenetre::addText(QString q)
{
    ui->textChat->append(q);
}

void Fenetre::addClient(QString q)
{
    ui->textClients->append(q);
}

void Fenetre::addPartie(QString q)
{
    ui->textParties->append(q);
}

void Fenetre::refreshClients()
{
    ui->textClients->clear();
    for (std::list<MyClient>::iterator i = clients.begin(); i != clients.end(); ++i)
    {
        this->addClient(QString(i->nom.c_str()));
    }
}

void Fenetre::refreshGames()
{
    ui->textParties->clear();
    defScreen->clearPartie();

    for (std::list<MyGame>::iterator i = games.begin(); i != games.end(); ++i)
    {
        std::ostringstream os1, os2;
        os1 << (int)i->nbJoueursAct;
        os2 << (int)i->nbJoueursMax;
        std::string ligne = os1.str() + "/" + os2.str() + " " + i->nom;
        this->addPartie(QString(ligne.c_str()));

        this->defScreen->addPartie(QString(ligne.c_str()));
    }
}

void Fenetre::deleteScreenAct()
{
    switch (scrAct)
    {
        case eDEF :
            delete defScreen;
            break;
        case eCFG :
            delete cfgGame;
            break;
        case eSAL :
            delete salScreen;
            break;
        case eCANV :
            delete canvasSfml;
            break;
    }
}

void Fenetre::quitter()
{
    _mythread->quitter();
    qApp->quit();
}

void Fenetre::lineChatReturn()
{
    sf::Packet p;
    p << eMAIN_NEWMSG;

    _client->send(p, true);

    std::string msg;
    msg = "[" + _client->_pseudo.toStdString() + "] >> " + ui->lineChat->text().toStdString();

    p.clear();
    p << msg;

    _client->send(p, true);
    ui->lineChat->setText("");
}

void Fenetre::newClient()
{
    MyClient mc;
    mc.nom = _mythread->getNomClient();
    clients.push_back(mc);
    this->addClient(QString(mc.nom.c_str()));
}

void Fenetre::newGame()
{
    MyGame mg;
    mg.nom = _mythread->getNomPartie();
    mg.nbJoueursAct = _mythread->getNbJAct();
    mg.nbJoueursAct = _mythread->getNbJMax();
    games.push_back(mg);

    std::ostringstream os1, os2;
    os1 << (int)mg.nbJoueursAct;
    os2 << (int)mg.nbJoueursMax;
    std::string ligne = os1.str() + "/" + os2.str() + " " + mg.nom;
    this->addPartie(QString(ligne.c_str()));

    this->defScreen->addPartie(QString(ligne.c_str()));

    if (DEBUG) {std::cout << "nom de la nouvelle partie : " << mg.nom << std::endl;}
}

void Fenetre::newMsg()
{
    this->addText(QString(_mythread->getMessage().c_str()));
}

void Fenetre::decoClient()
{
    for (std::list<MyClient>::iterator i = clients.begin(); i != clients.end(); ++i)
    {
        if(i->nom == _mythread->getNomClient())
        {
            clients.erase(i);
        }
    }
    refreshClients();
}

void Fenetre::decoGame()
{
    for (std::list<MyGame>::iterator i = games.begin(); i != games.end(); ++i)
    {
        if(i->nom == _mythread->getNomPartie())
        {
            games.erase(i);
        }
    }
    refreshGames();
}

void Fenetre::joinGame()
{
    sf::Packet p;
    p << eJOIN_GAME;

    _client->send(p, true);

    p.clear();

}

void Fenetre::createGame()
{
    deleteScreenAct();
    scrAct = eCFG;
    cfgGame = new ConfigGame(this, ui->wEmp1);
    cfgGame->show();
}

void Fenetre::sendNewGame()
{
    QString nom = cfgGame->getNomPartie();
    sf::Uint8 nbJ = cfgGame->getNbJoueurs();
    std::string nomP = nom.toStdString();
    if(! nom.isEmpty())
    {
        sf::Packet p;
        p << eNEW_GAME;
        _client->send(p, true);

        p.clear();

        p << nomP << nbJ;
        _client->send(p, true);
    }

    else
    {
        QMessageBox::critical(NULL, "Erreur", "Le nom de la partie est vide");
    }
}

void Fenetre::traitementCreateGame()
{
    if (_mythread->getValeurPartie() == 1)
    {
        deleteScreenAct();
        scrAct = eSAL;
        salScreen = new salonScreen(ui->wEmp1);
        salScreen->setNomPartie(_mythread->getNomPartie());

        salScreen->show();
    }
    else if (_mythread->getValeurPartie() == 0)
    {
        QMessageBox::critical(NULL, "Erreur", "La partie existe deja");
    }
}

void Fenetre::slotAddPartie()
{
    for (std::list<MyGame>::iterator i = games.begin(); i != games.end(); ++i)
    {
        if(i->nom == _mythread->getNomPartie())
        {
            i->nbJoueursAct++;
        }
    }
    refreshGames();
}

void Fenetre::slotRmPartie()
{
    for (std::list<MyGame>::iterator i = games.begin(); i != games.end(); ++i)
    {
        if(i->nom == _mythread->getNomPartie())
        {
            i->nbJoueursAct--;
        }
    }
    refreshGames();
}

void Fenetre::slotReady()
{
    sf::Packet p;
    p << eMAIN_READY;
    _client->send(p, false);
}

void Fenetre::slotLaunch()
{
    deleteScreenAct();
    scrAct = eCANV;
    canvasSfml = new MyCanvas(ui->wEmp1, QPoint(0, 0), QSize(801, 591));
    canvasSfml->show();

    // On recupere les nb envoyes sur le thread et on genere la map
}
